package com.huitone.smspfm.interfacz.model;

import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;

import com.alibaba.druid.support.json.JSONUtils;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.bin.common.utils.StringUtils;
import com.huitone.smspfm.interfacz.logger.ExtLogger;
import com.huitone.smspfm.interfacz.utils.SMSSpeedUtils;

/**
 * @Title SmsSpeedStatistics.java
 * @Package com.huitone.smspfm.interfacz.model
 * @Description 短信接入流速统计
 * @author ozh
 * @date
 * @version V1.0
 */
public class SmsSpeedStatistics {
	private static final ExtLogger logger = ExtLogger.create(SmsSpeedStatistics.class);
	private static DateFormat dateFormat = new SimpleDateFormat("yyyyMMddHHmmss");
	private volatile Map<Integer,Integer> secondMap;
	private volatile Map<Integer,Integer> minuteMap;
	private volatile Map<Integer,Integer> hourMap;
	private volatile Map<Integer,Integer> dayMap;
	private volatile Map<Integer,Integer> monthMap;

	private String resptime = "";
	
	
	public Map<Integer, Integer> getSecondMap() {
		return secondMap;
	}
	public void setSecondMap(Map<Integer, Integer> secondMap) {
		this.secondMap = secondMap;
	}
	public Map<Integer, Integer> getMinuteMap() {
		return minuteMap;
	}
	public void setMinuteMap(Map<Integer, Integer> minuteMap) {
		this.minuteMap = minuteMap;
	}
	public Map<Integer, Integer> getHourMap() {
		return hourMap;
	}
	public void setHourMap(Map<Integer, Integer> hourMap) {
		this.hourMap = hourMap;
	}
	public Map<Integer, Integer> getDayMap() {
		return dayMap;
	}
	public void setDayMap(Map<Integer, Integer> dayMap) {
		this.dayMap = dayMap;
	}
	public Map<Integer, Integer> getMonthMap() {
		return monthMap;
	}
	public void setMonthMap(Map<Integer, Integer> monthMap) {
		this.monthMap = monthMap;
	}
	public String getResptime() {
		return resptime;
	}
	public void setResptime(String resptime) {
		this.resptime = resptime;
	}
	private int getYear(){
		if(StringUtils.isEmpty(this.resptime) && this.resptime.length() < 14){
			return 0;
		}
		return StringUtils.toInteger(this.resptime.subSequence(0, 4));	
	}
	private int getMonth(){
		if(StringUtils.isEmpty(this.resptime) && this.resptime.length() < 14){
			return 0;
		}
		return StringUtils.toInteger(this.resptime.subSequence(4, 6));	
	}
	private int getDay(){
		if(StringUtils.isEmpty(this.resptime) && this.resptime.length() < 14){
			return 0;
		}
		return StringUtils.toInteger(this.resptime.subSequence(6, 8));	
	}
	private int getHour(){
		if(StringUtils.isEmpty(this.resptime) && this.resptime.length() < 14){
			return 0;
		}
		return StringUtils.toInteger(this.resptime.subSequence(8, 10));	
	}
	private int getMinute(){
		if(StringUtils.isEmpty(this.resptime) && this.resptime.length() < 14){
			return 0;
		}
		return StringUtils.toInteger(this.resptime.subSequence(10, 12));	
	}
	private  int getSecond(){
		if(StringUtils.isEmpty(this.resptime) && this.resptime.length() < 14){
			return 0;
		}
		return StringUtils.toInteger(this.resptime.subSequence(12, 14));	
	}
	
	public int getMonthCnt(int val){
		if(this.monthMap != null && timeFlag(Unit.MONTH)){
			return this.monthMap.containsKey(val) ? this.monthMap.get(val) : 0;
		}
		return 0;
	}
	public int getDayCnt(int val){
		if(this.dayMap != null && timeFlag(Unit.DATE)){
			return this.dayMap.containsKey(val) ? this.dayMap.get(val) : 0;
		}
		return 0;
	}
	public int getHourCnt(int val){
		if(this.hourMap != null && timeFlag(Unit.HOUR_OF_DAY)){
			return this.hourMap.containsKey(val) ? this.hourMap.get(val) : 0;
		}
		return 0;
	}
	private enum Unit{
		SECOND,MINUTE,HOUR_OF_DAY,DATE,MONTH,YEAR
	}
	public int getMinuteCnt(int val){
		if(this.minuteMap != null && timeFlag(Unit.SECOND)){
			return this.minuteMap.containsKey(val) ? this.minuteMap.get(val) : 0;
		}
		return 0;
	}
	private boolean timeFlag(Unit unit) {
		boolean timeFlag = false;
		Calendar cal = Calendar.getInstance();
		int year = cal.get(Calendar.YEAR);// 年份
		int month = cal.get(Calendar.MONTH)+1;// 获取月份
		int day = cal.get(Calendar.DATE);// 获取日
		int hour = cal.get(Calendar.HOUR_OF_DAY);// 小时
		int minute = cal.get(Calendar.MINUTE);// 分
		int second = cal.get(Calendar.SECOND);// 秒

		boolean exceedMinute = minute != getMinute();
		boolean exceedHour = hour != getHour();
		boolean exceedDay = day != getDay();
		boolean exceedMonth = month != getMonth();
		boolean exceedYear = year != getYear();
		switch (unit) {
		case SECOND:
			timeFlag = (!exceedYear && !exceedMonth && !exceedDay && !exceedHour && !exceedMinute);
			break;
		case MINUTE:
			timeFlag = (!exceedYear && !exceedMonth && !exceedDay && !exceedHour);
			break;
		case HOUR_OF_DAY:
			timeFlag = (!exceedYear && !exceedMonth && !exceedDay );
			break;
		case DATE:
			timeFlag = (!exceedYear && !exceedMonth);
			break;
		case MONTH:
			timeFlag = (!exceedYear);
			break;
		case YEAR:
			timeFlag = !exceedYear;
			break;

		default:
			timeFlag = false;
			break;
		}
		
		return timeFlag;
	}

	public int getSecondCnt(int val) {
		if (this.secondMap != null && timeFlag(Unit.SECOND)) {
			return this.secondMap.containsKey(val) ? this.secondMap.get(val)
					: 0;
		}
		return 0;

	}
	private Object mLock = new Object();

	public SmsSpeedStatistics() {
		Calendar cal = Calendar.getInstance();
		this.resptime = dateFormat.format(cal.getTime());
		this.monthMap = new HashMap<Integer, Integer>();
		this.dayMap = new HashMap<Integer, Integer>();
		this.hourMap = new HashMap<Integer, Integer>();
		this.minuteMap = new HashMap<Integer, Integer>();
		this.secondMap = new HashMap<Integer, Integer>();
	}
	
	public static SmsSpeedStatistics parseJson(String jsonString){
		SmsSpeedStatistics smsSpeed = new SmsSpeedStatistics();
		JSONObject json = JSONObject.parseObject(jsonString);
		String monthStr = (String) json.get("monthMap");
		String dayStr = (String) json.get("dayMap");
		String hourStr = (String) json.get("hourMap");
		String minuteStr = (String) json.get("minuteMap");
		String secondStr = (String) json.get("secondMap");
		String respTimeStr = (String) json.get("respTime");
		
		Calendar cal = Calendar.getInstance();
		if(! StringUtils.isEmpty(respTimeStr)){
			smsSpeed.resptime = respTimeStr;
		}

		if(! StringUtils.isEmpty(secondStr)){
			smsSpeed.secondMap = SMSSpeedUtils.toMap(secondStr);
		}
		if(! StringUtils.isEmpty(minuteStr)){
			smsSpeed.minuteMap = SMSSpeedUtils.toMap(minuteStr);
		}
		if(! StringUtils.isEmpty(hourStr)){
			smsSpeed.hourMap = SMSSpeedUtils.toMap(hourStr);
		}
		if(! StringUtils.isEmpty(dayStr)){
			smsSpeed.dayMap = SMSSpeedUtils.toMap(dayStr);
		}
		if(! StringUtils.isEmpty(monthStr)){
			smsSpeed.monthMap = SMSSpeedUtils.toMap(monthStr);
		}	
		return smsSpeed;
	}

	


	public String toRedisString() {
	
		String monthMapString = SMSSpeedUtils.maptoJsonString(monthMap);
		String dayMapString = SMSSpeedUtils.maptoJsonString(dayMap);
		String hourMapString = SMSSpeedUtils.maptoJsonString(hourMap);
		String minuteMapString = SMSSpeedUtils.maptoJsonString(minuteMap);
		String secondMapString = SMSSpeedUtils.maptoJsonString(secondMap);
		JSONObject json = new JSONObject();
		json.put("monthMap", monthMapString);
		json.put("dayMap", dayMapString);
		json.put("hourMap", hourMapString);
		json.put("minuteMap", minuteMapString);
		json.put("secondMap", secondMapString);
		json.put("respTime", this.resptime);
		return json.toJSONString();
	}

	public SmsSpeedStatistics add() {
		synchronized (mLock) {
			Calendar cal = Calendar.getInstance();
			int year = cal.get(Calendar.YEAR);// 年份
			int month = cal.get(Calendar.MONTH)+1;// 获取月份
			int day = cal.get(Calendar.DATE);// 获取日
			int hour = cal.get(Calendar.HOUR_OF_DAY);// 小时
			int minute = cal.get(Calendar.MINUTE);// 分
			int second = cal.get(Calendar.SECOND);// 秒

			boolean exceedMinute = minute != getMinute();
			boolean exceedHour = hour != getHour();
			boolean exceedDay = day != getDay();
			boolean exceedMonth = month != getMonth();
			boolean exceedYear = year != getYear();
			
			if(exceedYear){
				monthMap.clear();
				exceedMonth = true;
			}
			if(exceedMonth){
				dayMap.clear();
				exceedDay = true;
			}
			if(exceedDay){
				hourMap.clear();
				exceedHour = true;
			}
			if(exceedHour){
				minuteMap.clear();
				exceedMinute = true;
			}
			if(exceedMinute){
				secondMap.clear();
			}
			
			Integer val = 1;
			if(monthMap.containsKey(month)){
				monthMap.put(month, monthMap.get(month)+val); 
			}else{
				monthMap.put(month, val);
			}
			if(dayMap.containsKey(day)){
				dayMap.put(day, dayMap.get(day)+val); 
			}else{
				dayMap.put(day, val);
			}
			if(hourMap.containsKey(hour)){
				hourMap.put(hour, hourMap.get(hour)+val); 
			}else{
				hourMap.put(hour, val);
			}
			if(minuteMap.containsKey(minute)){
				minuteMap.put(minute, minuteMap.get(minute)+val); 
			}else{
				minuteMap.put(minute, val);
			}
			if(secondMap.containsKey(second)){
				secondMap.put(second, secondMap.get(second)+val); 
			}else{
				secondMap.put(second, val);
			}
			setResptime(dateFormat.format(cal.getTime()));
			return this;
		}
	}

	public boolean isTimeOut(long time, long smsSpeedTimeOut) {
		if (time == 0 || smsSpeedTimeOut <= 0) {
			return true;
		}

		boolean result = false;		
		try {
			Date date = dateFormat.parse(resptime);
			result = (date.getTime() + smsSpeedTimeOut) > time;
		} catch (ParseException e) {
			logger.error("Date conversion error");
		}

		return result;
	}
}
